package com.google.code.opencode.service.impl;

import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.Date;
import java.util.Iterator;
import java.util.List;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.code.opencode.model.Feed;
import com.google.code.opencode.service.Reader;
import com.sun.syndication.feed.synd.SyndEntry;
import com.sun.syndication.feed.synd.SyndFeed;
import com.sun.syndication.io.FeedException;
import com.sun.syndication.io.SyndFeedInput;
import com.sun.syndication.io.XmlReader;

/**
 * @author Cesar Arevalo
 * @since 0.0.1
 */
public class RSSReader implements Reader {

	private static Logger logger = LoggerFactory.getLogger(RSSReader.class);

	public static void main(String[] args) throws Exception {

		List<Feed> opencodeList = new ArrayList<Feed>();
		Feed opencodeFeed = new Feed();
		opencodeFeed.setUrl("http://sourceforge.net/export/rss2_projnews.php?group_id=84122");
		opencodeList.add(opencodeFeed);
		Reader reader = new RSSReader();

		for (Feed opencodeFeedFor : opencodeList) {
			logger.debug("reader.read(opencodeFeedFor): " + reader.read(opencodeFeedFor));
		}
	
	}

	@Override
	public String read(Feed opencodeFeed) {
		URL url = null;
		try {
			url = new URL(opencodeFeed.getUrl());
		} catch (MalformedURLException e) {
			e.printStackTrace();
		}
        SyndFeedInput input = new SyndFeedInput();
        SyndFeed feed = null;
		try {
			feed = input.build(new XmlReader(url));
		} catch (IllegalArgumentException e) {
			throw new UnsupportedOperationException(e);
		} catch (FeedException e) {
			throw new UnsupportedOperationException(e);
		} catch (IOException e) {
			throw new UnsupportedOperationException(e);
		}
        Iterator entryIter = feed.getEntries().iterator();

    	SyndEntry entry = (SyndEntry) entryIter.next();

    	/**
    	 * What are the different scenarios?
    	 * 
    	 * a) That this is the first feed.
    	 * b) That the entry.publishedDate is after the oF.lastPublishedDate
    	 * c) That the entry.updatedDate is after the oF.lastPublishedDate
    	 * 
    	 */
    	if (opencodeFeed.getLastPublishedDate() == null ||
    			(entry.getPublishedDate() != null && opencodeFeed.getLastPublishedDate().before(entry.getPublishedDate())) ||
    			(entry.getPublishedDate() == null && entry.getUpdatedDate() != null && opencodeFeed.getLastPublishedDate().before(entry.getUpdatedDate()))
    		) {

    		if (logger.isInfoEnabled() && opencodeFeed.getLastPublishedDate() != null) {
    	    	logger.info("<---- \n\n" +
    	    			"getTitle -> " + entry.getTitle() + " \n " +
    	                "getAuthor -> " + entry.getAuthor() + " \n " +
    	                "getPublishedDate -> " + entry.getPublishedDate() + " \n " +
    	                "getUpdatedDate -> " + entry.getUpdatedDate() + " \n " +
    	                "getLink -> " + entry.getLink() + " \n " +
    	                "getDescription -> " + (entry != null && entry.getDescription() != null ? entry.getDescription().getValue() : "") +
    	                "\n\n ---->");

    	    	logger.info("opencodeFeed.getLastPublishedDate: " + opencodeFeed.getLastPublishedDate());
    		}

    		if (entry.getPublishedDate() != null) {
        		opencodeFeed.setLastPublishedDate(entry.getPublishedDate());
    		}
    		else if (entry.getUpdatedDate() != null) {
        		opencodeFeed.setLastPublishedDate(entry.getUpdatedDate());
    		}
    		else {
    			opencodeFeed.setLastPublishedDate(new Date());
    		}

    		String returnValue = "";
    		if (entry.getTitle().length() > 106) {
    			returnValue = entry.getTitle().substring(0, 106);
    		}
    		else {
    			returnValue = entry.getTitle();
    		}
    		returnValue += "... " + entry.getLink();
        	return returnValue;
    	}
    	else {
    		return null;
    	}
	}

}
